using System;
using System.Collections.Generic;
using Habanero.Base;
using Habanero.Faces.Base;
using Habanero.Faces.Win;

namespace FireStarterModeller.UI
{
    /// <summary>
    /// Control for viewing and managing a list of errors and warnings for one or more business objects.
    /// </summary>
    public class ErrorViewerControl : UserControlWin
    {
        const string COLUMN_ERROR_MESSAGE = "ErrorMessage";
        const string COLUMN_VIEW_DETAILS = "ViewDetails";

        private readonly IDataGridView _gridControl;
        private readonly IControlFactory _controlFactory;

        public ErrorViewerControl() : this(GlobalUIRegistry.ControlFactory)
        {
        }

        public ErrorViewerControl(IControlFactory controlFactory)
        {
            if (controlFactory == null) throw new ArgumentNullException("controlFactory");
            _controlFactory = controlFactory;
            _gridControl = controlFactory.CreateDataGridView();
            _gridControl.Columns.Add("Source", "Source");
            IDataGridViewColumn column = controlFactory.CreateDataGridViewTextBoxColumn();
            column.Name = COLUMN_ERROR_MESSAGE;
            column.HeaderText = "ErrorMessage";
            column.Width = 400;
            _gridControl.Columns.Add(column);

            IDataGridViewImageColumn viewDetailsColumn = controlFactory.CreateDataGridViewImageColumn();
            viewDetailsColumn.Name = COLUMN_VIEW_DETAILS;
            viewDetailsColumn.HeaderText = "";
            viewDetailsColumn.Width = 60;
            _gridControl.Columns.Add(viewDetailsColumn);

            _gridControl.Columns.Add("ErrorLevel", "Level");
            _gridControl.ReadOnly = true;
            _gridControl.AllowUserToAddRows = false;
            _gridControl.AllowUserToDeleteRows = false;
            _gridControl.SelectionMode = DataGridViewSelectionMode.FullRowSelect;
            BorderLayoutManager layoutManager = controlFactory.CreateBorderLayoutManager(this);
            layoutManager.AddControl(_gridControl, BorderLayoutManager.Position.Centre);

            ((DataGridViewWin)_gridControl).CellClick += ErrorViewerControl_CellClick;
        }

        void ErrorViewerControl_CellClick(object sender, System.Windows.Forms.DataGridViewCellEventArgs e)
        {
            int imageColNumber = GetColumnNumber(COLUMN_VIEW_DETAILS);
            int messageColNumber = GetColumnNumber(COLUMN_ERROR_MESSAGE);
            if (e.ColumnIndex == imageColNumber)
            {
                string errorMessage = _gridControl.Rows[e.RowIndex].Cells[messageColNumber].Value.ToString();
                _controlFactory.ShowMessageBox(errorMessage);
            }
        }

        private int GetColumnNumber(string columnName)
        {
            return ((DataGridViewColumnWin)_gridControl.Columns[columnName]).DataGridViewColumn.Index;
        }

        /// <summary>
        /// Returns the Grid that the Errors are being shown in.
        /// </summary>
        public IDataGridView ErrorViewerGrid
        {
            get { return _gridControl; }
        }

        private IList<IBOError> _errorList;
        
        /// <summary>
        /// Gets and Sets the Error List that is being displayed in this <see cref="ErrorViewerControl"/>
        /// </summary>
        public IList<IBOError> ErrorList
        {
            get { return _errorList; }
            set
            {
                _errorList = value;
                PopulateGrid();
            }
        }

        private void PopulateGrid()
        {
            object[] values = new object[3];

            foreach (IBOError error in _errorList)
            {
                IBusinessObject businessObject = error.BusinessObject;
                if (businessObject == null) continue;

                values[0] = businessObject.ToString();
                values[1] = error.Message;
                values[2] = error.Level;
                int addedIndex = _gridControl.Rows.Add(values);
                IDataGridViewRow row = _gridControl.Rows[addedIndex];
                row.Tag = businessObject;
                row.Cells[GetColumnNumber(COLUMN_VIEW_DETAILS)].Value = FMResources.magnifying_glass;
            }
        }
    }
}